package com.hangzhou.xyj.ui.widget.views;

import com.hangzhou.xyj.R;

import android.content.Context;
import android.os.Parcelable;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.RecyclerView;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewConfiguration;
import android.view.ViewGroup;
import android.view.ViewTreeObserver;

/**
 * @author : neo.duan
 * @date : 	 2016/3/12
 * @desc : 自定义下拉刷新组件，便于需求变动
 * fix 不能横向滑动的事件的检测
 */
public class MySwipeRefreshLayout extends SwipeRefreshLayout{
    private final String TAG = "MySwipeRefreshLayout";

    private int mTouchSlop;
    private float mPrevX;
    // Indicate if we've already declined the move event
    private boolean mDeclined;

    private CanChildScrollUpCallback mCanChildScrollUpCallback;
    private RecyclerView.OnScrollListener mListener = new RecyclerView.OnScrollListener() {
        @Override
        public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
            int topRowVerticalPosition =
                    (recyclerView == null || recyclerView.getChildCount() == 0) ? 0 : recyclerView.getChildAt(0).getTop();
            setEnabled(topRowVerticalPosition >= 0);
        }

        @Override
        public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
            super.onScrolled(recyclerView, dx, dy);
        }
    };
    private boolean selfCancelled = false;

    public MySwipeRefreshLayout(Context context, AttributeSet attrs) {
        super(context, attrs);
        mTouchSlop = ViewConfiguration.get(context).getScaledTouchSlop();
        initView();
    }

    public MySwipeRefreshLayout(Context context) {
        super(context, null);
        initView();
    }

    public void setCanChildScrollUpCallback(CanChildScrollUpCallback canChildScrollUpCallback) {
        mCanChildScrollUpCallback = canChildScrollUpCallback;
    }

    private void initView() {
        Log.d(TAG, "initView");
        this.setColorSchemeResources(R.color.common_purple,
                R.color.common_purple,
                R.color.common_purple,
                R.color.common_purple);
        this.setSize(SwipeRefreshLayout.DEFAULT);
        //swipeRefreshLayout.setPadding(20, 20, 20, 20);
        //swipeRefreshLayout.setProgressViewOffset(true, 100, 200);
        //swipeRefreshLayout.setDistanceToTriggerSync(50);
//        this.setProgressViewEndTarget(true, 100);

        //View绘制完回调
        this.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
            @Override
            public void onGlobalLayout() {
                /**
                 * 解决下拉刷新与RecyclerView冲突问题
                 */
                View childView = getChildAt(0);
                //是ViewGroup则继续遍历
                if (childView != null && childView instanceof ViewGroup) {
                    RecyclerView recyclerView = findRecyclerView((ViewGroup) childView);
                    if (recyclerView == null) {
                        getViewTreeObserver().removeGlobalOnLayoutListener(this);
                        return;
                    }
                    if (recyclerView instanceof MyRecyclerView) {
                        recyclerView.addOnScrollListener(mListener);
                    } else {
                        recyclerView.setOnScrollListener(mListener);
                    }
                    getViewTreeObserver().removeGlobalOnLayoutListener(this);
                }
            }
        });
    }

    /**
     * 递归找到 RecyclerView
     * @param viewGroup
     * @return
     */
    private RecyclerView findRecyclerView(ViewGroup viewGroup) {
        Log.d(TAG, "find findRecyclerView()");
        for (int i = 0; i < viewGroup.getChildCount(); i++) {
            Log.d(TAG,"find getChildCount i===" + i);
            View childView = viewGroup.getChildAt(i);
            if (childView instanceof RecyclerView) {
                Log.d(TAG,"find RecyclerView");
                return (RecyclerView) childView;
            } else if (childView instanceof ViewGroup){
                return findRecyclerView((ViewGroup) childView);
            }
        }
        return null;
    }

    @Override
    public boolean onInterceptTouchEvent(MotionEvent event) {

        switch (event.getAction()) {
            case MotionEvent.ACTION_DOWN:
                MotionEvent obtain = MotionEvent.obtain(event);
                mPrevX = obtain.getX();
                mDeclined = false; // New action

                break;

            case MotionEvent.ACTION_MOVE:
                final float eventX = event.getX();
                float xDiff = Math.abs(eventX - mPrevX);

                if (mDeclined || xDiff > mTouchSlop) {
                    mDeclined = true; // Memorize
                    return false;
                }


        }

        return super.onInterceptTouchEvent(event);
    }


    @Override
    public boolean canChildScrollUp() {


        if (mCanChildScrollUpCallback != null) {
            return mCanChildScrollUpCallback.canSwipeRefreshChildScrollUp();
        }
        return super.canChildScrollUp();
    }

    @Override
    public void requestDisallowInterceptTouchEvent(boolean b) {
        super.requestDisallowInterceptTouchEvent(b);
    }

    @Override
    protected Parcelable onSaveInstanceState() {
        if (isRefreshing()) {
            clearAnimation();
            setRefreshing(false);
            selfCancelled = true;
            Log.d(TAG, "For hide refreshing");
        }
        return super.onSaveInstanceState();
    }

    @Override
    public void setRefreshing(boolean refreshing) {
        super.setRefreshing(refreshing);
        selfCancelled = false;
    }

    @Override
    public void onWindowFocusChanged(boolean hasWindowFocus) {
        super.onWindowFocusChanged(hasWindowFocus);
        if (hasWindowFocus && selfCancelled) {
            setRefreshing(true);
            Log.d(TAG, "Force show refreshing");
        }
    }

    public interface CanChildScrollUpCallback {
        boolean canSwipeRefreshChildScrollUp();
    }
}
